package com.haidechizi.i18n.common.utils;

import com.haidechizi.i18n.common.config.Configuration;
import com.haidechizi.i18n.common.enums.LanguageTypeEnum;
import com.haidechizi.i18n.common.enums.annotation.I18nKey;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.context.ApplicationListener;
import org.springframework.context.MessageSource;
import org.springframework.context.event.ContextRefreshedEvent;

import java.util.Locale;

/**
 * 国际化工具类，
 * 可以国际化一些提示信息，以及枚举类
 */
@Slf4j
public class I18nUtils implements ApplicationListener<ContextRefreshedEvent> {

    private static MessageSource messageSource;

    private static Configuration configuration;

    public I18nUtils(MessageSource messageSource) {
        I18nUtils.messageSource = messageSource;
    }

    /**
     * 翻譯message.properties中的國際化資源按code翻譯， 如果沒有取得request中的local信息，默認使用fanti中文 這個方法是spring i18n
     * service的簡便調用方式，使用時，請確保當前調用棧處于spring環境下
     */
    public static String translate(String code) {
        return translate(code, getLanguage(), null);
    }

    public static String translate(String code, Object[] args) {
        return translate(code, getLanguage(), args);
    }

    public static String translate(String code, String localeParam) {
        return translate(code, localeParam, null);
    }

    public static String translate(String code, String localeParam, Object[] args) {

        Locale locale = null;
        if (StringUtils.isNotEmpty(localeParam)) {
            String[] split = localeParam.split("_");
            locale = new Locale(split[0], split[1]);
        } else {
            locale = new Locale("zh", "HK");
        }
        locale = locale == null ? new Locale("zh", "HK") : locale;
        return messageSource.getMessage(code, args, locale);
    }

    public static String translateForEnum(String locale, Enum enumInstance) {
        if (StringUtils.isEmpty(locale) || enumInstance == null) {
            return null;
        }
        try {
            String name = enumInstance.name();
            I18nKey i18nKey = enumInstance.getClass().getField(name).getAnnotation(I18nKey.class);
            if (i18nKey == null) {
                log.warn("current enum:{} don't have I18nKey annotation!", enumInstance);
                return null;
            } else {
                String code = i18nKey.value();
                return translate(code, locale);
            }
        } catch (Exception e) {
            log.error("translate enum i18n error", e);
            return null;
        }

    }

    public static String translateForEnum(Enum enumInstance) {
        if (messageSource == null) {
            log.warn("no messageSource injected,do not translate");
            return null;
        }
        return translateForEnum(getLanguage(), enumInstance);
    }

    /**
     * 当前线程是否是英文
     */
    public static Boolean ifEnUSCurrentThread() {
        String locale = getLanguage();
        return LanguageTypeEnum.en_US.getCode().equals(locale);
    }

    public static String getLanguage() {
        String language = GlobalUtils.getLanguage();
        if (StringUtils.isNotBlank(language)) {
            return language;
        }
        language = RequestUtils.getLocale(configuration.getI18nLocale());
        if (StringUtils.isNotBlank(language)) {
            return language;
        }
        return configuration.getDefaultLanguage();
    }

    @Override
    public void onApplicationEvent(ContextRefreshedEvent contextRefreshedEvent) {
        configuration = contextRefreshedEvent.getApplicationContext().getBean(Configuration.class);
    }
}
